let a = [1, 2, 3];
var b = ["a", "b"];
const c: boolean[] = [true, false];
const d: Array<string> = ["a", "b"];

let e = [1, "a"];
const f: Array<string | number> = ["a", "b", 2];

a.push(4);
// a.push("a"); //error
d.unshift("c");

f.push("aaa");
// f.push(true); //error

let g = [1, "a"];
g.map(item => { 
  if (typeof item === "number") {
    return item * 2;
  }
  return item.toUpperCase();
})

type User = {
  name: string;
  age: number;
}

const users: Array<User> = [
  {
    name: "a",
    age: 20
  },
  {
    name: "b",
    age: 21
  }
];

const arr = [];
arr.push(1);
arr.push("a");

// 如果any类型的数组在函数中有赋值了具体的类型，那么出了函数作用域之后，就不会被扩展为any[]类型
function fn() { 
  const arr = [];

  arr.push(1);
  arr.push("a");
  return arr;
}

const arr2 = fn();
// arr2.push(true);

const arr3: readonly number[] = [1, 2, 3];
const myArr1 = arr3.concat(4);
console.log(myArr1);

const myArr2 = arr3.filter(item => item > 2);
console.log(myArr2)

const myArr3 = arr3.slice(0, 2);
console.log(myArr3)

// arr3.push(4);
// arr3[3] = 4;
// arr3.splice(0, 1);

// 可以是number数组，可以是string，也可以是number和string类型混合的数组
type ArrType1 = (number | string)[]; 
// 要么是number类型，要么是string类型
type ArrType2 = number[] | string[];

const arr1: ArrType1 = ["a", "b", "c"];
const arr6: ArrType2 = [1, 2, 3];
// const arr7: ArrType2 = [1, "a", 3]; // error
const arr8: ArrType1 = [1, "a", 3];

const pointer1: number[] = [10, 20];
const pointer2: readonly [number, number] = [20, 30];

// 具名元组
const pointer3: [x: number, y: number] = [30, 40];

const user: [name: string, age: number, gender: "男" | "女"] = ["jack", 20, "女"];


//元组存在的问题
// 虽然不能通过下标添加数组元素，但是可以通过push方法添加元素，我们可以将元组设置为只读readonly元组
// pointer2[2] = 40;
// pointer2.push(40);